package ldk.easytouch.helper;

import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.content.IntentFilter;
import android.graphics.PixelFormat;
import android.graphics.Point;
import android.os.Handler;
import android.view.Gravity;
import android.view.KeyEvent;
import android.view.MotionEvent;
import android.view.View;
import android.view.WindowManager;
import android.widget.FrameLayout;

import java.util.LinkedList;

import ldk.easytouch.activity.BaseActivity;
import ldk.easytouch.interfaces.IActivity;
import ldk.easytouch.utils.ETLog;

/**
 * Created by ldkxingzhe on 2016/9/13.
 */
public class InstrumentHelper{
    @SuppressWarnings("unused")
    private static final String TAG = "InstrumentHelper";

    private LinkedList<IActivity> mActivityStack;
    private RootView mRootView;
    private WindowManager.LayoutParams mRootWindowLayoutParams;
    private WindowManager mWindowManager;

    private Handler mHandler;

    private static InstrumentHelper s_Instance;
    public static InstrumentHelper getInstance(){
        if(s_Instance == null){
            s_Instance = new InstrumentHelper();
        }
        return s_Instance;
    }

    public void init(Context context, IActivity activity){
        if(mRootView != null) throw new IllegalStateException("function init should only call once");
        mRootView = new RootView(context);
        registerBroadcastReceiver();
        PositionHelper.getInstance().readFromCache(context);

        mWindowManager = (WindowManager) context.getSystemService(Context.WINDOW_SERVICE);
        mRootWindowLayoutParams = new WindowManager.LayoutParams();
        mRootWindowLayoutParams.type = WindowManager.LayoutParams.TYPE_SYSTEM_ALERT;
        mRootWindowLayoutParams.width = WindowManager.LayoutParams.WRAP_CONTENT;
        mRootWindowLayoutParams.height = WindowManager.LayoutParams.WRAP_CONTENT;
        mRootWindowLayoutParams.format = PixelFormat.TRANSPARENT;
        mRootWindowLayoutParams.gravity = Gravity.START|Gravity.TOP;
        Point leftUpPoint = PositionHelper.getInstance().getOriginPointLeftUp();
        mRootWindowLayoutParams.x = leftUpPoint.x;
        mRootWindowLayoutParams.y = leftUpPoint.y;
        mWindowManager.addView(mRootView, mRootWindowLayoutParams);
        onStartActivity(activity, null);
        ETLog.v(TAG, "init");
    }

    private InstrumentHelper(){
        mActivityStack = new LinkedList<>();
        mHandler = new Handler();
    }

    public void updateXY(int left, int top){
        mRootWindowLayoutParams.x = left;
        mRootWindowLayoutParams.y = top;
        updateLayoutParams(mRootWindowLayoutParams);
    }

    public void updateLayoutParams(WindowManager.LayoutParams params){
        mWindowManager.updateViewLayout(mRootView, params);
    }

    public FrameLayout getRootView(){
        return mRootView;
    }

    /* 获取当前的Activity */
    public IActivity getCurrentActivity(){
        if(mActivityStack.isEmpty()){
            return null;
        }
        return mActivityStack.getLast();
    }

    public void onStartActivity(final IActivity activity, Runnable runnable){
        if(runnable != null){
            runnable.run();
        }else{
            IActivity currentActivity = getCurrentActivity();
            if(currentActivity != null) {
                currentActivity.onStop();
                View currentContentView = currentActivity.getContentView();
                removeView(currentContentView);
            }
            activity.onCreate();
            mHandler.post(new Runnable() {
                @Override
                public void run() {
                    activity.getContentView().setVisibility(View.VISIBLE);
                    activity.onUpdateWindowLayoutParams(mRootWindowLayoutParams);
                    updateLayoutParams(mRootWindowLayoutParams);
                    activity.onResume();
                }
            });
        }
        mActivityStack.add(activity);
    }

    public void addView(View contentView){
        mRootView.addView(contentView);
        contentView.setVisibility(View.INVISIBLE);
    }

    public void removeView(View contentView){
        mRootView.removeView(contentView);
    }

    public void onFinish(BaseActivity baseActivity) {
        baseActivity.onStop();
        baseActivity.onDestroy();
        removeView(baseActivity.getContentView());
        mActivityStack.remove(baseActivity);
        if(!mActivityStack.isEmpty()){
            getCurrentActivity().onUpdateWindowLayoutParams(mRootWindowLayoutParams);
            updateLayoutParams(mRootWindowLayoutParams);
            mHandler.post(new Runnable() {
                @Override
                public void run() {
                    addView(getCurrentActivity().getContentView());
                    getCurrentActivity().getContentView().setVisibility(View.VISIBLE);
                    getCurrentActivity().onResume();
                }
            });
        }
    }

    private void registerBroadcastReceiver() {
        IntentFilter screenFilter = new IntentFilter();
        screenFilter.addAction(Intent.ACTION_SCREEN_ON);
        screenFilter.addAction(Intent.ACTION_SCREEN_OFF);
        screenFilter.addAction(Intent.ACTION_USER_PRESENT);
        mRootView.getContext().registerReceiver(mScreenOnOffReceiver, screenFilter);
    }

    private BroadcastReceiver mScreenOnOffReceiver = new BroadcastReceiver() {
        @Override
        public void onReceive(Context context, Intent intent) {
            if(getCurrentActivity() == null) return;
            String action = intent.getAction();
            ETLog.v(TAG, "onScreenOnOffReceiver, and action is %s.", action);
            switch (action){
                case Intent.ACTION_SCREEN_ON:
                    break;
                case Intent.ACTION_SCREEN_OFF:
                    getCurrentActivity().onStop();
                    break;
                case Intent.ACTION_USER_PRESENT:
                    getCurrentActivity().onResume();
                    break;
            }
        }
    };

    private class RootView extends FrameLayout implements View.OnTouchListener {

/*        @Override
        public boolean onInterceptTouchEvent(MotionEvent ev) {
            int rawX = (int) ev.getRawX();
            int rawY = (int) ev.getRawY();
            ETLog.v(TAG, "rawX is %d, and rawY is %d.", rawX, rawY);
            return super.onInterceptTouchEvent(ev);
        }*/

        public RootView(Context context) {
            super(context);
            setOnTouchListener(this);
            requestFocus();
            setFocusable(true);
            setFocusableInTouchMode(true);
        }

        @Override
        public boolean onTouch(View v, MotionEvent event) {
            if(event.getAction() == MotionEvent.ACTION_DOWN){
                getCurrentActivity().onTouchOutside();
            }
            return false;
        }

        @Override
        public boolean onKeyDown(int keyCode, KeyEvent event) {
            ETLog.v(TAG, "onKeyDown, and keyCode %d.", keyCode);
            getCurrentActivity().onKeyDown(keyCode, event);
            return true;
        }
    }
}
